<!DOCTYPE html>
<html lang="en"><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
<title>examplethree</title>
  
<!-- Based on mrdoob's Clouds demo -->

<meta charset="utf-8">
<style type="text/css">

  body {
    background-color: #82a2c2;
    margin: 0px;
    overflow: hidden;
    font-family:Monospace;
    font-size:13px;
    text-align:center;
    font-weight: bold;
    text-align:center;
  }

  a {
    color:#0078ff;
  }

</style>
<body>

<script type="text/javascript" src="./scripts/ThreeWebGL.js"></script>
<script type="text/javascript" src="./scripts/ThreeExtras.js"></script>

<script type="text/javascript" src="./scripts/Detector.js"></script>
<script type="text/javascript" src="./scripts/RequestAnimationFrame.js"></script>

<script id="vs" type="x-shader/x-vertex">

  varying vec2 vUv;

  void main() {

    vUv = uv;
    gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );

  }

</script>

<script id="fsFog" type="x-shader/x-fragment">
  
  uniform sampler2D map;
  
  uniform vec3 fogColor;
  uniform float fogNear;
  uniform float fogFar;
  
  varying vec2 vUv;
  
  void main() {
    
    float depth = gl_FragCoord.z / gl_FragCoord.w;
    float fogFactor = smoothstep( fogNear, fogFar, depth );
    
    gl_FragColor = texture2D( map, vUv );
    gl_FragColor.w *= pow( gl_FragCoord.z, 20.0 );
    gl_FragColor = mix( gl_FragColor, vec4( fogColor, gl_FragColor.w ), fogFactor );
    
  }
  
</script>
  
<script type="text/javascript">

  if ( ! Detector.webgl ) Detector.addGetWebGLMessage();
  
  var fieldSize = 1500;

  var container;
  var camera, scene, renderer, sky, geometry, material,
  i, h, color, colors = [], sprite, size;
  var ship;
  var shipVel = new THREE.Vector2();

  var mouseX = 0, mouseY = 0;
  var lastTime = new Date().getTime();
  var keyDown = [];

  var windowHalfX = window.innerWidth / 2;
  var windowHalfY = window.innerHeight / 2;

  init();
  animate();

  function init() {

    container = document.createElement( 'div' );
    document.body.appendChild( container );

    camera = new THREE.Camera( 30, window.innerWidth / window.innerHeight, 1, 2000 );
    camera.position.z = 300;

    scene = new THREE.Scene();
    scene.fog = new THREE.Fog( 0x82a2c2, - 100, 1200 );

    // Build clouds

    var cloudTex = THREE.ImageUtils.loadTexture( 'resources/cloud10.png' );
    cloudTex.magFilter = THREE.LinearMipMapLinearFilter;
    cloudTex.minFilter = THREE.LinearMipMapLinearFilter;

    cloudMaterial = new THREE.MeshBasicMaterial( {

      fog: true,
      depthTest: false,
      map: cloudTex,
      transparent: true

    } );

    var plane = new THREE.Mesh( new THREE.PlaneGeometry( 64, 64 ) );
    var geometry = new THREE.Geometry();

    for ( var i = -500; i < 0; i += 1 ) {

      plane.position.x = Math.random() * fieldSize;
      plane.position.y = Math.random() * fieldSize;
      plane.position.z = i;
      plane.rotation.z = ( Math.random() - 0.5 ) * Math.PI * 0.5;
      plane.scale.x = plane.scale.y = Math.random() * Math.random() * 1.0 + 1.0;

      THREE.GeometryUtils.merge( geometry, plane );

    }

    for ( var x = -1; x <= 1; ++x ) {
      for ( var y = -1; y <= 1; ++y ) {
        var mesh = new THREE.Mesh( geometry, cloudMaterial );
        mesh.position.x = x * fieldSize;
        mesh.position.y = y * fieldSize;
        scene.addObject( mesh );
      }
    }
    
    // Build ship
    
    var shipTex = THREE.ImageUtils.loadTexture( 'resources/spaceship.png' );
    shipTex.magFilter = THREE.LinearMipMapLinearFilter;
    shipTex.minFilter = THREE.LinearMipMapLinearFilter;
    
    shipMaterial = new THREE.MeshBasicMaterial( {

      map: shipTex, depthTest: false, transparent: true

    } );
    
    ship = new THREE.Mesh( new THREE.PlaneGeometry( 20, 20 ), shipMaterial );
    scene.addObject(ship);
    
    // Add some more clouds on top
    
    var geometry = new THREE.Geometry();

    for ( var i = 0; i < 50; i += 1 ) {
      
      plane.position.x = Math.random() * fieldSize;
      plane.position.y = Math.random() * fieldSize;
      plane.position.z = i;
      plane.rotation.z = ( Math.random() - 0.5 ) * Math.PI * 0.5;
      plane.scale.x = plane.scale.y = Math.random() * Math.random() * 1.0 + 1.0;
      
      THREE.GeometryUtils.merge( geometry, plane );
      
    }
    
    for ( var x = -1; x <= 1; ++x ) {
      for ( var y = -1; y <= 1; ++y ) {
        var mesh = new THREE.Mesh( geometry, cloudMaterial );
        mesh.position.x = x * fieldSize;
        mesh.position.y = y * fieldSize;
        scene.addObject( mesh );
      }
    }
    
    renderer = new THREE.WebGLRenderer( { antialias: false } );
    renderer.setSize( window.innerWidth, window.innerHeight );
    renderer.sortObjects = false;
    container.appendChild( renderer.domElement );

    document.addEventListener( 'mousemove', onDocumentMouseMove, false );
    document.addEventListener( 'keydown', onDocumentKeyDown, false );
    document.addEventListener( 'keyup', onDocumentKeyUp, false );
    window.addEventListener( 'resize', onWindowResize, false );

  }

  function onDocumentMouseMove( event ) {

    mouseX = ( event.clientX - windowHalfX ) * 0.25;
    mouseY = ( event.clientY - windowHalfY ) * 0.15;

  }

  function onDocumentKeyDown( event ) {

    keyDown[ event.keyCode ] = true;
    
  }
  
  function onDocumentKeyUp( event ) {
    
    keyDown[ event.keyCode ] = false;
    
  }
  
  function onWindowResize( event ) {

    camera.aspect = window.innerWidth / window.innerHeight;
    camera.updateProjectionMatrix();

    renderer.setSize( window.innerWidth, window.innerHeight );

  }

  function animate() {

    render();
    requestAnimationFrame( animate );

  }

  function render() {

    var nowTime = new Date().getTime();
    var deltaTime = nowTime - lastTime;
    lastTime = nowTime;
    
    if ( deltaTime > 0 ) {

      // Update ship according to user input
      
      if ( keyDown[ 37 ] ) ship.rotation.z += deltaTime * 0.005;
      if ( keyDown[ 39 ] ) ship.rotation.z -= deltaTime * 0.005;
      if ( keyDown[ 38 ] ) {
        
        shipVel.x -= Math.sin( ship.rotation.z ) * deltaTime * 0.001;
        shipVel.y += Math.cos( ship.rotation.z ) * deltaTime * 0.001;

      }

      ship.position.x += shipVel.x * deltaTime;
      ship.position.y += shipVel.y * deltaTime;
      
      shipVel.x /= ( 1 + deltaTime * 0.002 );
      shipVel.y /= ( 1 + deltaTime * 0.002 );
      
      // Wrap the ship around at field edges

      if ( ship.position.x < 0 ) {
        ship.position.x += fieldSize;
        camera.position.x += fieldSize;
      }
      if ( ship.position.x >= fieldSize ) {
        ship.position.x -= fieldSize;
        camera.position.x -= fieldSize;
      }
      if ( ship.position.y < 0 ) {
        ship.position.y += fieldSize;
        camera.position.y += fieldSize;
      }
      if ( ship.position.y >= fieldSize ) {
        ship.position.y -= fieldSize;
        camera.position.y -= fieldSize;
      }
      
      var targetX = ship.position.x;
      var targetY = ship.position.y;
      
      // Move camera smoothly towards target position

      camera.position.x = targetX + ( camera.position.x - targetX ) / ( 1 + deltaTime * 0.02 );
      camera.position.y = targetY + ( camera.position.y - targetY ) / ( 1 + deltaTime * 0.02 );

    }

    renderer.render( scene, camera );

  }

</script>

</body>
</html>